package controller

import (
	"bytes"
	"context"
	"encoding/json"
	"fmt"
	"io"
	"log"
	"myginproject/internal/controller/ws"
	"myginproject/internal/models"
	"net/http"
	"time"

	"github.com/gin-gonic/gin"
	"github.com/google/uuid"
	"gorm.io/gorm"
)

// 创建群组
// AddGroup 创建群组（从URL获取参数，仅存储到Redis）
// AddGroup 创建群组（直接使用Redis客户端）
func AddGroup(hub *ws.Hub) gin.HandlerFunc {
	return func(c *gin.Context) {
		// 1. 首先读取原始请求体（用于调试）
		rawData, _ := c.GetRawData()
		fmt.Printf("Raw request: %s\n", string(rawData))

		fmt.Printf("c.ContentType(): %s\n", c.ContentType())

		// 2. 重新绑定到上下文（因为GetRawData消耗了reader）
		c.Request.Body = io.NopCloser(bytes.NewBuffer(rawData))

		// 3. 定义请求结构
		var req struct {
			GroupID   string `json:"group_id" binding:"required"`
			GroupName string `json:"group_name" binding:"required"`
		}

		// 4. 绑定JSON
		if err := c.ShouldBindJSON(&req); err != nil {
			fmt.Printf("Bind error: %v\n", err) // 打印具体绑定错误
			c.JSON(http.StatusBadRequest, gin.H{
				"error":  "参数绑定失败",
				"detail": err.Error(),
				"code":   -1,
			})
			return
		}
		fmt.Printf("req: %s\n", req)
		// 从URL路径获取参数
		groupID := req.GroupID
		fmt.Printf("groupID: %s\n", groupID)
		groupName := req.GroupName
		fmt.Printf("groupName: %s\n", groupName)
		// 验证参数
		if groupID == "" || groupName == "" {
			c.JSON(http.StatusBadRequest, gin.H{
				"error": "群组ID和名称不能为空",
				"code":  -1,
			})
			return
		}

		ctx := context.Background()

		// 检查群组是否已存在
		exists, err := hub.GetRedis().Exists(ctx, "WsGroup:"+groupID).Result()
		if err != nil {
			log.Printf("Redis查询错误: %v", err)
			c.JSON(http.StatusInternalServerError, gin.H{
				"error": "服务器内部错误",
				"code":  -1,
			})
			return
		}

		if exists == 1 {
			c.JSON(http.StatusConflict, gin.H{
				"error": "群组已存在",
				"code":  200,
			})
			return
		}

		// 创建群组信息
		groupKey := "WsGroup:" + groupID
		// 6. 创建群组信息（使用map确保参数正确）
		// 写法2：确保参数数量正确（每个字段名后必须跟一个值）
		// 写法1：最可靠的map方式
		groupData := map[string]interface{}{
			"id":         req.GroupID,
			"name":       req.GroupName,
			"created_at": time.Now().Format(time.RFC3339),
		}
		fmt.Printf("groupData: %v\n", groupData)
		err = hub.GetRedis().HSet(ctx, groupKey, groupData).Err()

		if err != nil {
			log.Printf("Redis存储群组信息失败: %v", err)
			c.JSON(http.StatusInternalServerError, gin.H{
				"error": "创建群组失败",
				"code":  -1,
			})
			return
		}

		// 设置过期时间（可选）
		hub.GetRedis().Expire(ctx, groupKey, 30*24*time.Hour)

		c.JSON(http.StatusOK, gin.H{
			"message":    "群组创建成功",
			"group_id":   groupID,
			"group_name": groupName,
			"code":       200,
		})
	}
}

// 群消息发送接口
func SendGroupMessage(db *gorm.DB, hub *ws.Hub) gin.HandlerFunc {
	return func(c *gin.Context) {
		// 1. 首先读取原始请求体（用于调试）
		rawData, _ := c.GetRawData()
		fmt.Printf("Raw request: %s\n", string(rawData))

		// 2. 重新绑定到上下文（因为GetRawData消耗了reader）
		c.Request.Body = io.NopCloser(bytes.NewBuffer(rawData))

		// 3. 定义请求结构
		var req struct {
			GroupID  string          `json:"group_id" binding:"required"`
			UserID   string          `json:"user_id" binding:"required"`
			UserName string          `json:"user_name" binding:"required"`
			Avatar   string          `json:"avatar"`
			Content  json.RawMessage `json:"content" binding:"required"`
		}

		// 4. 绑定JSON
		if err := c.ShouldBindJSON(&req); err != nil {
			fmt.Printf("Bind error: %v\n", err) // 打印具体绑定错误
			c.JSON(http.StatusBadRequest, gin.H{
				"error":  "参数绑定失败",
				"detail": err.Error(),
				"code":   -1,
			})
			return
		}

		ctx := context.Background()
		// 检查群组是否已存在
		exists, err := hub.GetRedis().Exists(ctx, "WsGroup:"+req.GroupID).Result()
		if err != nil {
			log.Printf("Redis查询错误: %v", err)
			c.JSON(http.StatusInternalServerError, gin.H{
				"error": "服务器内部错误",
				"code":  -1,
			})
			return
		}

		if exists != 1 {
			c.JSON(http.StatusConflict, gin.H{
				"error": "群组不存在",
				"code":  -1,
			})
			return
		}

		// 6. 创建消息
		msg := &models.WsMessage{
			Event:     "message",
			MsgID:     uuid.New().String(),
			GroupID:   req.GroupID,
			SenderID:  req.UserID,
			Sender:    req.UserName,
			Avatar:    req.Avatar,
			Content:   string(req.Content),
			Timestamp: time.Now(),
		}

		// 7. 广播消息
		hub.Broadcast <- msg

		c.JSON(http.StatusOK, gin.H{
			"status":    "success",
			"msg_id":    msg.MsgID,
			"group_id":  msg.GroupID,
			"timestamp": msg.Timestamp.Unix(),
		})
	}
}
